---
title: Getting started
---

import Tabs from "@theme/Tabs";
import TabItem from "@theme/TabItem";

Before diving into the inner mechanisms of [Riverpod], let's start with the basics:
Installing up [Riverpod], then writing a "Hello world".

You can also watch this video which explains the problems that [Riverpod] tries
to solve.

<div class="player">
  <iframe
    src="https://www.youtube.com/embed/zjBulEwjzeI"
    frameborder="0"
    allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture"
    allowfullscreen
  ></iframe>
</div>

(Note: this video does not explain how [Riverpod] works. It only explains the
problems)

## What package to install

Before anything, you need to be aware that [Riverpod] is spread across multiple packages, with slightly different usage.  
The variant of [Riverpod] that you will want to install depends on the app you are making.

You can refer to the following table to help you decide which package to use:

| app type                  | package name                                                                       | description                                                                          |
| ------------------------- | ---------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------ |
| Flutter + [flutter_hooks] | [hooks_riverpod]                                                                   | A way to use both [flutter_hooks] and [Riverpod] together, while offering small extras. |
| Flutter only              | [flutter_riverpod]                                                                 | A basic way of using [Riverpod], which does not depend on [flutter_hooks].           |
| Dart only (No Flutter)    | [riverpod](https://github.com/rrousselGit/river_pod/tree/master/packages/riverpod) | A version of [Riverpod] with all the classes related to Flutter stripped out.            |

And if it's not clear enough, you can refer to this decision graph:

![package decision graph](/img/package_decision_graph.svg)

## Installing the package

Once you know what package you want to install, proceed to add the following to your `pubspec.yaml`:

<Tabs
  groupId="riverpod"
  defaultValue="hooks_riverpod"
  values={[
    { label: 'Flutter + flutter_hooks', value: 'hooks_riverpod', },
    { label: 'Flutter', value: 'flutter_riverpod', },
    { label: 'Dart only', value: 'riverpod', },
  ]}
>
<TabItem value="hooks_riverpod">

```yaml title="pubspec.yaml"
environment:
  sdk: ">=2.7.0 <3.0.0"
  flutter: ">=1.17.0"

dependencies:
  flutter:
    sdk: flutter
  flutter_hooks: ^0.14.0
  hooks_riverpod: ^0.12.1
```

Then run `flutter pub get`.

</TabItem>
<TabItem value="flutter_riverpod">

```yaml title="pubspec.yaml"
environment:
  sdk: ">=2.7.0 <3.0.0"
  flutter: ">=1.17.0"

dependencies:
  flutter:
    sdk: flutter
  flutter_riverpod: ^0.12.1
```

Then run `flutter pub get`.

</TabItem>
<TabItem value="riverpod">

```yaml title="pubspec.yaml"
environment:
  sdk: ">=2.7.0 <3.0.0"

dependencies:
  riverpod: ^0.12.1
```

Then run `pub get`.

</TabItem>
</Tabs>

That's it. You've added [Riverpod] to your app!

## Usage example: Hello world

Now that we have installed [Riverpod], we can start using it.

The following snippets showcase our to use our new dependency to make a "Hello world":

<Tabs
  groupId="riverpod"
  defaultValue="hooks_riverpod"
  values={[
    { label: "Flutter + flutter_hooks", value: "hooks_riverpod" },
    { label: "Flutter", value: "flutter_riverpod" },
    { label: "Dart only", value: "riverpod" },
  ]}
>
<TabItem value="hooks_riverpod">

```dart title="lib/main.dart"
import 'package:flutter/material.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:flutter_hooks/flutter_hooks.dart';

// We create a "provider", which will store a value (here "Hello world").
// By using a provider, this allows us to mock/override the value exposed.
final helloWorldProvider = Provider((_) => 'Hello world');

void main() {
  runApp(
    // For widgets to be able to read providers, we need to wrap the entire
    // application in a "ProviderScope" widget.
    // This is where the state of our providers will be stored.
    ProviderScope(
      child: MyApp(),
    ),
  );
}

// Note: MyApp is a HookWidget, from flutter_hooks.
class MyApp extends HookWidget {
  @override
  Widget build(BuildContext context) {
    // To read our provider, we can use the hook "useProvider".
    // This is only possible because MyApp is a HookWidget.
    final String value = useProvider(helloWorldProvider);

    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(title: Text('Example')),
        body: Center(
          child: Text(value),
        ),
      ),
    );
  }
}
```

Which you can then execute with `flutter run`.  
This will render "Hello world" in on your device.

</TabItem>
<TabItem value="flutter_riverpod">

```dart title="lib/main.dart"
import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';

// We create a "provider", which will store a value (here "Hello world").
// By using a provider, this allows us to mock/override the value exposed.
final helloWorldProvider = Provider((_) => 'Hello world');

void main() {
  runApp(
    // For widgets to be able to read providers, we need to wrap the entire
    // application in a "ProviderScope" widget.
    // This is where the state of our providers will be stored.
    ProviderScope(
      child: MyApp(),
    ),
  );
}

// Extend ConsumerWidget instead of StatelessWidget, which is exposed by Riverpod
class MyApp extends ConsumerWidget {
  @override
  Widget build(BuildContext context, ScopedReader watch) {
    final String value = watch(helloWorldProvider);

    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(title: Text('Example')),
        body: Center(
          child: Text(value),
        ),
      ),
    );
  }
}
```

Which you can then execute with `flutter run`.  
This will render "Hello world" in on your device.

</TabItem>
<TabItem value="riverpod">

```dart title="lib/main.dart"
import 'package:riverpod/riverpod.dart';

// We create a "provider", which will store a value (here "Hello world").
// By using a provider, this allows us to mock/override the value exposed.
final helloWorldProvider = Provider((_) => 'Hello world');

void main() {
  // This object is where the state of our providers will be stored.
  final container = ProviderContainer();

  // Thanks to "container", we can read our provider.
  final value = container.read(helloWorldProvider);

  print(value); // Hello world
}
```

Which you can then execute with `dart lib/main.dart`.  
This will print "Hello world" in the console.

</TabItem>
</Tabs>

## Going further: Installing code snippets

If you are using `Flutter` and `Vscode` consider [Flutter Riverpod Snippets](https://marketplace.visualstudio.com/items?itemName=robert-brunhage.flutter-riverpod-snippets)

If you are using `Flutter` and `Android Studio` or `IntelliJ` consider [Flutter Riverpod Snippets](https://plugins.jetbrains.com/plugin/14641-flutter-riverpod-snippets)

![img](/img/snippets/greetingProvider.gif)

[riverpod]: https://github.com/rrousselgit/river_pod
[hooks_riverpod]: https://pub.dev/packages/hooks_riverpod
[flutter_riverpod]: https://pub.dev/packages/flutter_riverpod
[flutter_hooks]: https://github.com/rrousselGit/flutter_hooks
